跳到主要内容

GPU Canvas

GPU Canvas 用于在 Apple 运行时中启用 3D 内容。它通过 Swift Concurrency API 提供,并在创建 Worker 时进行配置。该设置对该 worker 加载的每一个 File 以及由这些文件创建的每一个 Rive 对象生效。

渲染 3D 内容必须启用 GPU Canvas。

启用 GPU Canvas​

创建 worker 时,传入 enableGPUCanvas 为 true 的配置:

let worker = try await Worker(
configuration: .init(enableGPUCanvas: true)
)

Worker 的 GPU Canvas 设置在其整个生命周期内是固定的。请在加载任何需要 GPU Canvas 或 3D 支持的文件之前启用它。

使用该 worker 创建的每个 File 都会沿用同一设置:

let worker = try await Worker(
configuration: .init(enableGPUCanvas: true)
)
let file = try await File(
source: .local("my_file", Bundle.main),
worker: worker
)
let rive = try await Rive(file: file)

创建 RiveUIView、RiveUIViewRepresentable 或 AsyncRiveUIViewRepresentable 时无需额外配置。每个视图都会从其 Rive 对象所关联的 worker 继承 GPU Canvas 设置。

默认行为​

GPU Canvas 默认处于关闭状态。当你的内容不需要它时,仍可按不带配置的方式创建 worker:

let worker = try await Worker()

共享 GPU Canvas Worker​

当多个文件或视图可以共用同一个 worker 时,可以共享一个 GPU Canvas worker。下面是一个示例实现。

下面的 AsyncShared 以及 Worker 扩展属于应用层的辅助代码,并不包含在 RiveRuntime 中。

📌 AsyncShared.swift

/// 懒加载并缓存一个值。初始化失败后可以重试。
@MainActor
final class AsyncShared<Value> {
private let makeValue: @MainActor () async throws -> Value
private var cachedValue: Value?
private var loadingTask: Task<Value, Error>?

init(_ makeValue: @escaping @MainActor () async throws -> Value) {
self.makeValue = makeValue
}

func value() async throws -> Value {
if let cachedValue {
return cachedValue
}

let task = loadingTask ?? Task {
defer { loadingTask = nil }
let value = try await makeValue()
cachedValue = value
return value
}
loadingTask = task

return try await task.value
}
}

📌 AsyncShared+Worker.swift

import RiveRuntime

extension AsyncShared where Value == Worker {
convenience init(configuration: Worker.Configuration = .init()) {
self.init {
try await Worker(configuration: configuration)
}
}
}

extension Worker {
@MainActor
private static let sharedWorker = AsyncShared<Worker>()

@MainActor
private static let sharedGPUCanvasWorker = AsyncShared<Worker>(
configuration: .init(enableGPUCanvas: true)
)

@MainActor
static func shared() async throws -> Worker {
try await sharedWorker.value()
}

@MainActor
static func sharedGPUCanvas() async throws -> Worker {
try await sharedGPUCanvasWorker.value()
}
}

在加载需要 GPU Canvas 的文件时,使用 Worker.sharedGPUCanvas():

let worker = try await Worker.sharedGPUCanvas()
let file = try await File(
source: .local("my_file", Bundle.main),
worker: worker
)
let rive = try await Rive(file: file)

完整的设置示例请参阅 Apple 快速开始。

看完还有疑问?进群交流下!
与众多 Rive 创作者、开发者一起交流探讨与答疑解惑。
加入交流群